package projet.volleystat.automate;

import java.util.ArrayList;
import java.util.Map;
import java.util.TreeMap;

import projet.volleystat.DBInfo;
import projet.volleystat.DatabaseException;
import projet.volleystat.Player;
import projet.volleystat.Team;
import projet.volleystat.bdd.VolleyOpenhelper;

public class VolleyStatistic {
	private DBInfo db;

	public VolleyStatistic(DBInfo db) {
		this.db = db;
	}

	private TreeMap<String, Double> internAnalysis(ArrayList<TreeMap<String, Integer> > request) {
		TreeMap<String, Double> res = new TreeMap<String, Double>();
		int idAction = 0;
		res.put("service", 0.0);
		res.put("faute", 0.0);
		res.put("passe", 0.0);
		res.put("point", 0.0);
		res.put("reception", 0.0);
		res.put("remplacement", 0.0);
		res.put("scorePoint", 0.0);
		res.put("scoreReception", 0.0);
		res.put("scorePass", 0.0);
		for(TreeMap<String, Integer> map : request) {
			idAction = map.get(VolleyOpenhelper.Statistic_Columns_IDACTION);
			if(idAction < 30) {
				idAction = 0;
			}
			switch (idAction) {
			case 0:
				res.put("faute", res.get("faute")+1);
				break;
			case 30:
				res.put("point", res.get("point")+1);
				res.put("scorePoint", res.get("scorePoint")+map.get(VolleyOpenhelper.Statistic_Columns_MARK));
				break;
			case 31:
				res.put("remplacement", res.get("remplacement")+1);
				break;
			case 32:
				res.put("service", res.get("service")+1);
				break;
			case 35:
				res.put("reception", res.get("reception")+1);
				res.put("scoreReception", res.get("scoreReception")+map.get(VolleyOpenhelper.Statistic_Columns_MARK));
				break;
			case 36:
				res.put("passe", res.get("passe")+1);
				res.put("scorePass", res.get("scorePass")+map.get(VolleyOpenhelper.Statistic_Columns_MARK));
				break;
			}
		}
		res.put("scorePoint", 
				res.get("point") == 0 ? -1 : res.get("scorePoint")/res.get("point"));
		res.put("scoreReception", 
				res.get("reception") == 0 ? -1 : res.get("scoreReception")/res.get("reception"));
		res.put("scorePass", 
				res.get("passe") == 0 ? -1 : res.get("scorePass")/res.get("passe"));
		return res;
	}

	/**
	 * @param idPlayer
	 * @return TreeMap<String, Double>
	 * @throws DatabaseException
	 * Recupere un tableau associatif des statistiques d'un joueur tel que les clefs-valeurs sont :
	 * service : Nombre de service effectue.
	 * faute : Nombre de faute effectue.
	 * passe : Nombre de passe effectue.
	 * point : Nombre de point marque effectue.
	 * reception : Nombre de reception effectue.
	 * remplacement : Nombre de remplacement effectue.
	 * scorePoint : Moyenne des notes pour les points marquees.
	 * scoreReception : Moyenne des notes pour les receptions.
	 * scorePass : Moyenne des notes pour les passes.
	 * scorePoint : Moyenne des notes pour les points marquees.
	 */
	public TreeMap<String, Double> analysisPlayer(int idPlayer) throws DatabaseException {
		return internAnalysis(db.playerStat(idPlayer));
	}

	public TreeMap<Integer, TreeMap<String, Double> > analysisTeam(int idTeam) throws DatabaseException {
		TreeMap<Integer, TreeMap<String, Double> > res = new TreeMap<Integer, TreeMap<String, Double> >();
		Team team = db.getLoadedTeam().get(idTeam);
		int idPlayer = 0;
		if(team != null) {
			for(Player player : team.getPlayerlist()) {
				idPlayer = player.getId();
				res.put(idPlayer, analysisPlayer(idPlayer));
			}
		}
		return res;
	}

	/**
	 * @param idPlayer
	 * @param idMatch
	 * @return TreeMap<String, Double>
	 * @throws DatabaseException
	 * Recupere un tableau associatif des statistiques d'un joueur durant un match tel que les clefs-valeurs sont :
	 * service : Nombre de service effectue.
	 * faute : Nombre de faute effectue.
	 * passe : Nombre de passe effectue.
	 * point : Nombre de point marque effectue.
	 * reception : Nombre de reception effectue.
	 * remplacement : Nombre de remplacement effectue.
	 * scorePoint : Moyenne des notes pour les points marquees.
	 * scoreReception : Moyenne des notes pour les receptions.
	 * scorePass : Moyenne des notes pour les passes.
	 * scorePoint : Moyenne des notes pour les points marquees.
	 * ratioServiceDurantMatch : ratio (entre 0 et 1) du nombre de services effectues par le joueur sur le nombre de services sur le match.
	 * ratioFauteDurantMatch : ratio (entre 0 et 1) du nombre de fautes effectuees par le joueur sur le nombre de fautes sur le match.
	 * ratioPasseDurantMatch : ratio (entre 0 et 1) du nombre de passes effectuees par le joueur sur le nombre de passes sur le match.
	 * ratioPointDurantMatch : ratio (entre 0 et 1) du nombre de points marquees par le joueur sur le nombre de points marquees sur le match.
	 * ratioReceptionDurantMatch : ratio (entre 0 et 1) du nombre de receptions effectuees par le joueur sur le nombre de receptions sur le match.
	 * ratioRemplacementDurantMatch : ratio (entre 0 et 1) du nombre de remplacements du joueur sur le nombre de remplacements sur le match.
	 */
	public TreeMap<String, Double> analysisPlayerDuringMatch(int idPlayer, int idMatch) throws DatabaseException {		
		TreeMap<String, Double> StatPlayer = internAnalysis(db.playerStatDuringMatch(idPlayer, idMatch));
		TreeMap<String, Double> StatMatch = internAnalysis(db.matchStat(idMatch));
		StatPlayer.put("ratioServiceDurantMatch", 
				StatMatch.get("service") == 0 ? -1 : StatPlayer.get("service")/StatMatch.get("service"));
		StatPlayer.put("ratioFauteDurantMatch", 
				StatMatch.get("faute") == 0 ? -1 : StatPlayer.get("faute")/StatMatch.get("faute"));
		StatPlayer.put("ratioPasseDurantMatch", 
				StatMatch.get("passe") == 0 ? -1 : StatPlayer.get("passe")/StatMatch.get("passe"));
		StatPlayer.put("ratioPointDurantMatch", 
				StatMatch.get("point") == 0 ? -1 : StatPlayer.get("point")/StatMatch.get("point"));
		StatPlayer.put("ratioReceptionDurantMatch", 
				StatMatch.get("reception") == 0 ? -1 : StatPlayer.get("reception")/StatMatch.get("reception"));
		StatPlayer.put("ratioRemplacementDurantMatch", 
				StatMatch.get("remplacement") == 0 ? -1 : StatPlayer.get("remplacement")/StatMatch.get("remplacement"));
		return StatPlayer;
	}

	public TreeMap<String, String> formatResult(TreeMap<String, Double> result){
		TreeMap<String, String> res = new TreeMap<String, String>();
		for(Map.Entry<String, Double> entry : result.entrySet()){
			if(entry.getKey() == "service"){
				res.put(entry.getKey(), Long.toString(Math.round(entry.getValue())));
			}
			if(entry.getKey() == "faute"){
				res.put(entry.getKey(), Long.toString(Math.round(entry.getValue())));
			}
			if(entry.getKey() == "point"){
				res.put(entry.getKey(), Long.toString(Math.round(entry.getValue())));
			}
			if(entry.getKey() == "passe"){
				res.put(entry.getKey(), Long.toString(Math.round(entry.getValue())));
			}
			if(entry.getKey() == "reception"){
				res.put(entry.getKey(), Long.toString(Math.round(entry.getValue())));
			}
			if(entry.getKey() == "remplacement"){
				res.put(entry.getKey(), Long.toString(Math.round(entry.getValue())));
			}
			if(entry.getKey() == "scorePoint"){
				res.put(entry.getKey(), 
						entry.getValue() == -1 ? "N/A" :  Long.toString(Math.round(entry.getValue())));	
			}
			if(entry.getKey() == "scoreReception"){
				res.put(entry.getKey(), 
						entry.getValue() == -1 ? "N/A" :  Long.toString(Math.round(entry.getValue())));	
			}
			if(entry.getKey() == "scorePass"){
				res.put(entry.getKey(), 
						entry.getValue() == -1 ? "N/A" :  Long.toString(Math.round(entry.getValue())));	
			}
			if(entry.getKey() == "ratioServiceDurantMatch"){
				res.put(entry.getKey(), 
						entry.getValue() == -1 ? "N/A" :  Long.toString(Math.round(entry.getValue()*100)).concat("%"));	
			}
			if(entry.getKey() == "ratioFauteDurantMatch"){
				res.put(entry.getKey(), 
						entry.getValue() == -1 ? "N/A" :  Long.toString(Math.round(entry.getValue()*100)).concat("%"));	
			}
			if(entry.getKey() == "ratioPasseDurantMatch"){
				res.put(entry.getKey(), 
						entry.getValue() == -1 ? "N/A" :  Long.toString(Math.round(entry.getValue()*100)).concat("%"));	
			}
			if(entry.getKey() == "ratioPointDurantMatch"){
				res.put(entry.getKey(), 
						entry.getValue() == -1 ? "N/A" :  Long.toString(Math.round(entry.getValue()*100)).concat("%"));	
			}
			if(entry.getKey() == "ratioReceptionDurantMatch"){
				res.put(entry.getKey(), 
						entry.getValue() == -1 ? "N/A" :  Long.toString(Math.round(entry.getValue()*100)).concat("%"));	
			}
			if(entry.getKey() == "ratioRemplacementDurantMatch"){
				res.put(entry.getKey(), 
						entry.getValue() == -1 ? "N/A" :  Long.toString(Math.round(entry.getValue()*100)).concat("%"));	
			}
		}
		return res;
	}

	public TreeMap<Integer, TreeMap<String, Double> > analysisTeamDuringMatch(int idTeam, int idMatch) throws DatabaseException {
		TreeMap<Integer, TreeMap<String, Double> > res = new TreeMap<Integer, TreeMap<String, Double> >();
		Team team = db.getLoadedTeam().get(idTeam);
		int idPlayer = 0;
		if(team != null) {
			for(Player player : team.getPlayerlist()) {
				idPlayer = player.getId();
				res.put(idPlayer, analysisPlayerDuringMatch(idPlayer, idMatch));
			}
		}
		return res;
	}

	public TreeMap<String, Double> analysisMatch(int idMatch) throws DatabaseException {
		return internAnalysis(db.matchStat(idMatch));
	}
}
